var localDB = require('nedb');

var app = require('electron').remote;
const appPath = app.app.getPath('appData') + '\\Requester';

// 验证IP是否符合规范
var checkIpRegExp = function (ip) {
    var reStr = /^(1\d{2}|2[0-4]\d|25[0-5]|[1-9]\d|[1-9])\.(1\d{2}|2[0-4]\d|25[0-5]|[1-9]\d|\d)\.(1\d{2}|2[0-4]\d|25[0-5]|[1-9]\d|\d)\.(1\d{2}|2[0-4]\d|25[0-5]|[1-9]\d|\d)$/;
    var re = new RegExp(reStr);
    return re.test(ip) ? true : false;
};

// 验证端口是否符合规范
var checkPortRegExp = function (port) {
    var reStr = /^([0-9]|[1-9]\d{1,3}|[1-5]\d{4}|6[0-5]{2}[0-3][0-5])$/;
    var re = new RegExp(reStr);
    return re.test(port) ? true : false;
};

// 验证不能为空
var notNull = function (str) {
    if (str == "" || str == undefined || str == null || str == NaN) return false;
    var re = new RegExp("^[ ]+$");
    return !re.test(str);
};

var formatDoc = function (doc) {
    if ((typeof doc == 'object') && doc.constructor == Object) {
        var data = doc;
        data.id = doc._id;
        data.createdAt = doc.createdAt.getTime();
        data.updatedAt = doc.updatedAt.getTime();
        delete data.disable;
        delete data._id;
        return data;
    } else {
        return doc;
    };
};
// 格式化多行数据
var formatDocs = function (docs) {
    var _array = [];
    for (let i = 0; i < docs.length; i++) {
        const item = formatDoc(docs[i]);
        _array.push(item);
    };
    return _array;
};

var ConfigData = function () {
    this.db = new localDB({
        filename: appPath + '/data/dbConfig.db',
        autoload: true,
        timestampData: true,
    });
};

var insertDB = function (data, cb, db) {
    db.insert({
        type: data.type, // mongo loacl
        ip: data.ip,
        port: data.port,
        DBName: data.DBName,
        username: data.username,
        password: data.password,
        PorjectName: data.PorjectName,
        title: data.title,
        description: data.description,
        disable: false,
    }, (error, doc) => {
        if (error) {
            cb(error, null);
        } else {
            cb(false, formatDoc(doc));
        };
    });
};

ConfigData.prototype.creatDB = function (data, cb) {
    if (data.type == 'netMongo') {
        if (!checkIpRegExp(data.ip)) {
            cb('error IP', null);
            return;
        };
        if (!checkPortRegExp(data.port)) {
            cb('error port', null);
            return;
        };
        if (!notNull(data.DBName)) {
            cb('error DBName', null);
            return;
        };
        this.db.find({
            DBName: data.DBName,
            ip: data.ip,
            port: data.port,
            PorjectName: data.PorjectName
        }, (err, docs) => {
            if (err) {
                cb(error, null);
            } else if (docs.length >= 1) {
                cb('错误 ：数据库中已经存在了该 项目名 =>' + data.PorjectName, null);
            } else {
                insertDB(data, cb, this.db);
            }
        });
    } else {
        if (!notNull(data.PorjectName)) {
            cb('error DBName', null);
            return;
        };
        this.db.find({
            DBName: { $exists: false },
            ip: { $exists: false },
            port: { $exists: false },
            PorjectName: data.PorjectName
        }, (err, docs) => {
            if (err) {
                cb(error, null);
            } else if (docs.length >= 1) {
                cb('错误 ：数据库 : 中已经存在了该 项目名 ：' + data.PorjectName, null);
            } else {
                insertDB(data, cb, this.db);
            }
        });
    };
};
ConfigData.prototype.deleteDB = function (id, cb) {
    this.db.update({ _id: id }, { $set: { disable: true } }, function (error, doc) {
        if (error) {
            cb(error, null);
        } else {
            cb(false, doc);
        };
    })
};
ConfigData.prototype.updateDB = function (id, data, cb) {
    this.db.update({ _id: id }, {
        $set: {
            ip: data.ip,
            port: data.port,
            DBName: data.DBName,
            username: data.username,
            password: data.password,
            title: data.title,
            type: data.type,
            description: data.description,
        }
    }, function (error, doc) {
        if (error) {
            cb(error, null);
        } else {
            cb(false, doc);
        };
    });
};
ConfigData.prototype.getAllDB = function (cb) {
    // this.db.find({ $not: { disable: true } }, function (error, docs) {
    // });
    this.db
        .find({ $not: { disable: true } })
        .sort({ createdAt: 1 })
        .exec(function (error, docs) {
            if (error) {
                cb(error, null);
            } else {
                cb(false, formatDocs(docs));
            };
        });
};
ConfigData.prototype.getById = function (id, cb) {
    this.db.findOne({ _id: id }, (err, doc) => {
        if (err) {
            cb(error, null);
        } else {
            cb(false, formatDoc(doc));
        }
    })
};

module.exports = function () {
    return new ConfigData();
};